<!doctype HTML>
<html>
    <head>
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8"/>
        
        <title>Node Editor Documentation</title>
        
        <link rel="stylesheet" type="text/css" href="NodeEditorDoc_Resources/NodeEditorDoc.css"/>
        
    </head>

    <body>
        <br/>
        <br/>
        <br/>
        
        <div id="TitlePage" class="page">
            <h1>NODE EDITOR</h1>
            <P class="pMid ftLrgLbl">Free and versatile Node Editor Framework for Unity 3D</P>
            
            <br/>
            
            <P class="pMid">
                <img class="img" src="NodeEditorDoc_Resources/NodeEditorTitle.png"/>
                <br/>
                <span class="ftImgDesc">(Texture Composer, an example avaiable on the forums)</span>
            </P>
            
            <br/>
            
            <P class="pMid">
                <span class="ftLrgLbl">Documentation by <A href="http://forum.unity3d.com/members/seneral.638015/">Seneral</A></span>
                <br/>
                <span class="ftNrmLbl">Version 1.02 (30.01.16)</span>
            </P>
            
            <br/>
            
            <P class="pMid ftLrgLbl">
                <A href="https://github.com/Baste-RainGames/Node_Editor">Repository</A> 
                - 
                <A href="http://forum.unity3d.com/threads/simple-node-editor.189230/#post-2134738">Forums</A>
            </P>
        </div>
       
        <br/>
        <br/>
        <br/>
        <br/>
        
        <div id="ContentsPage" class="page">
            <h2>Contents</h2>
            
            <P class="pMid">
                <a class="ftLrgLbl" href="#PrefacePage">Preface</a> <br/>
                <span class="ftNrmLbl">Features</span> <br/>
                <span class="ftNrmLbl">Examples</span> <br/>
                <br/>
                
                <a class="ftLrgLbl" href="#GettingStartedPage">Getting Started</a> <br/>
                <span class="ftNrmLbl">Custom Nodes</span> <br/>
                <span class="ftNrmLbl">Custom ConnectionTypes</span> <br/>
                <br/>
                
                <a class="ftLrgLbl" href="#CustomizationPage">Customization</a> <br/>
                <span class="ftNrmLbl">Interface</span> <br/>
                <span class="ftNrmLbl">Framework Overview</span> <br/>
                <br/>
                
                <a class="ftLrgLbl" href="#EventsPage">Events</a> <br/>
                <br/>
                
                <a class="ftLrgLbl" href="#ConclusionPage">Conclusion</a> 
            </P>
            
        </div>
        
        <br/>
        <br/>
        <br/>
        <br/>
        
        <div id="PrefacePage" class="page">
            <h2>Preface</h2>
            <P>
                This Documentation intends to give you an overview of the Node Editor. It was initially posted by me, <A href="http://forum.unity3d.com/members/seneral.638015/">Seneral</A>, 
                as a personal project on the <A href="http://forum.unity3d.com/threads/simple-node-editor.189230/#post-2134738">Unity forums</A>. 
                After receiving a great amount of positive feedback I continued improving and supporting it, now featuring alot of major things a Node Editor needs to have! <br/>
                The <A href="https://github.com/Baste-RainGames/Node_Editor">GitHub repository</A> was set up by <A href="http://forum.unity3d.com/members/baste.185905/">Baste</A> during the early developement, 
                and now it's the main platform to share and contribute to Node Editor.
            </P>
            <br/>
            
            <h3>Features</h3>
            <P>The Node Editor is special in that it's open source, but still is packed full of features, some of which are very unique to this project and which we're proud of featuring:</P>
            <ul>
                <li>Full interface featuring all expected controls like zooming/panning</li>
                <li>Flexible and interchangeable GUI</li>
                <li>Canvas and Editor State system featuring alot of advanced controls</li>
                <li>Super easy to extend with custom nodes and types without modifying the provided code</li>
                <li>Flexible calculation system, soon supporting for state-like behaviour</li>
                <li>Extreme Node customization to create totally unique node appearances achieved by a custom windowing system</li>
                <li>Growing Runtime support, including every bit from the EditorWindow</li>
            </ul>
            <P>The framework also shines with clean and easy to modify code. It's clearly seperated in multiple parts, some of which can even be taken and used somewhere else, such as the unique, generic scaling approach!</P>
            <br/>
            
            <h3>Examples</h3>
            <P>
                You can start off by checking out the Editor Window at '<var>Window/Node Editor</var>' and loading one of the example canvases, such as the CalculationCanvas. 
                Do that by either loading it with the button at the top right or by locating it in the project folder and double-clicking it. <br/>
                With right-click you can add additional nodes, using drag'n'drop you can connect node Outputs and Inputs with each other.
            </P>
        </div>
        
        <br/>
        <br/>
        <br/>
        <br/>
        
        <div id="GettingStartedPage" class="page">
            <h2>Getting Started</h2>
            <P>
                Here you'll find some help on how to get you started creating custom Nodes and ConnectionTypes in the simplest form, without touching the Framework code. 
                These two methods already can help you make little extensions requiring the Node Editor Framework to be installed seperately.
            </P>
            <br/>
            
            <h3>Custom Nodes</h3>
            <P>
                The implementation of additional, custom nodes is fairly easy. You have to create a script anywhere in the project extending the Node class of the <code>NodeEditorFramework</code> namespace. 
                It will provide the Framework all needed information about the node itself, the optional <code>Node</code> Attribute contains information about the presentation in the editor. 
                The Framework will search all script assemblies for additional nodes, so extra setup is not required. <br/>
                In the following are the necessary Node members outlined, based upon the ExampleNode found at '<var>Plugins/Node_Editor/Nodes</var>'. 
                First to mention is that even though the Framework is programmed in C#, you can add nodes in UnityScript with the limitation that they have to be compiled in phase 2,3 or 4, 
                as described <A href="http://docs.unity3d.com/Manual/ScriptCompileOrderFolders.html">here</A>. Therefore the following members are described language independently.
            </P>
            <ul>
                <li><b><code>NodeEditorFramework</code> dependency</b></li>
                <li><b>Class extending <code>Node</code></b></li>
                <li><i>Optional:</i> <b>Attribute <code>Node</code></b> <var>[Params: [Bool] hide; [String] contextPath]</var></li>
                <li><b>Unique Node ID</b>; declare: <code>ID</code> <var>[constant string]</var>; expose: property <code>GetID</code> <var>[override]</var></li>
                <br/>
                <li>
                    <i>Optional:</i> <b>Behaviour Options</b>
                    <ul>
                        <li><code>AllowRecursion</code> <var>[override, default: false]</var></li>
                        <li><code>ContinueCalculation</code> <var>[override, default: true]</var></li>
                        <li><code>AcceptsTransitions</code> <var>[override, default: false]</var></li>
                    </ul> 
                </li>
                <br/>
                <li>
                    <b>Method <code>Create</code></b> <var>[override; Params: [Vector2] position; Return: [Node] Created Node]</var>
                    <ul>
                        <li>Create a <u>new Instance of your node type</u> using <code>CreateInstance</code>. Assign it's property <code>rect</code> using the position parameter and give it a name.</li>
                        <li><u>Add connections</u> using <code>CreateInput/CreateOutput</code> or <code>NodeInput.Create</code> / <code>NodeOutput.Create</code> <var>[Params: Name; TypeName; NodeSide; position]</var></li>
                        <li>Perform any other additional setup steps and return your created node</li>
                    </ul> 
                </li>
                <br/>
                <li>
                    <b>Method <code>NodeGUI</code></b> <var>[override]</var>
                    <ul>
                        <li>Draw your <u>Node's GUI</u> in it. You may use GUILayout funtions</li>
                        <li><u>Access the Inputs/Outputs</u> using the Inputs/Outputs array in the creation order. Use their methods <code>DisplayLayout</code> or <code>SetPosition</code> to position (and draw) them</li>
                    </ul> 
                </li>
                <br/>
                <li>
                    <b>Method <code>Calculate</code></b> <var>[override; Returns: [Bool] Calculation success]</var>
                    <ul>
                        <li>The methods <code>allInputsReady</code>, <code>hasUnassignedInputs</code> and <code>descendantsCalculated</code> may help to check <u>if the node is ready</u>, based on the needs and purposes of it.</li>
                        <li>Access the inputs as described above, call <code>GetValue</code> to <u>get the value stored in the connection</u> of the same type. Similarily, <u>set the output values</u> with <code>SetValue</code>.</li>
                        <li>
                            Return true when you're <u>done calculating</u> and false when you are <u>not ready yet</u> and need another attempt. 
                            But be aware, you cannot yield calculation that way, after a maximum of a thousand repeated tries the calculation will be aborted!
                        </li>
                    </ul>
                </li>
            </ul>
            <br/>
            
            <h3>Custom ConnectionTypes</h3>
            <P>
                Implementing custom ConnectionTypes is similar to Node implementation, as it uses the same fetching system: 
                Declare a class inheriting from the <code>ITypeDeclaration</code> interface and specify it's properties.
            </P>
            
            <P class="pMid">
                <IMG class="img" src="NodeEditorDoc_Resources/ConnectionTypes.png"/>
                <br/>
                <span class="ftImgDesc">ConnectionTypes.cs: Top Block: ITypeDeclaration; Bottom Block: Built-in Float type</span>
            </P>
            
            <ul>
                <li>The <var>string name</var> is used to adress the type later on</li>
                <li>The <var>Color col</var> is the color associated with the type, and the following knob textures aswell as the node connection curves are tinted with it</li>
                <li>
                    The strings <var>InputKnob_TexPath</var> and <var>OutputKnob_TexPath</var> are the paths to the input and output knob textures <b>relative to <var>Node_Editor/Resources</var></b>. 
                    Defaults are <var>Textures/In_Knob.png</var> and <var>Textures/Out_Knob.png</var>.
                </li>
                <li>The type this declaration representates (e.g. 'typeof(float)') is stored in the <b>Type 'Type'</b>.</li>
            </ul>
        </div>
        
        <br/>
        <br/>
        <br/>
        <br/>
       
        <div id="CustomizationPage" class="page">
            <h2>Customizing</h2>
            <P>
                Even though you can already built small extensions with methods described above pretty well, to natively integrate Node Editor into your 
                own editor extension you may want to cutomize it, from building your own editor interface to modifying and extending the framework itself.
            </P>
            <br/>
            
            <h3>Interface</h3>
            <P>
                The provided Editor Window basically serves as the default Node Canvas explorer for all dependant extensions and single canvases, 
                but also as a starting point to develop a custom Editor Window from. That means, you can savely delete it if you don't want it in your extension. 
                In the following I'll outline all things you need to consider to build a basic Node Editor Interface in both Runtime and the Editor.
            </P>
            <br/>
            
            <h4>Saving and Loading Canvas and Editor State</h4>
            <P>
                The Editor needs to store the currently opened Canvas (<code>NodeCanvas</code>) and it's Editor State (<code>NodeEditorState</code>). 
                For an explanation of these, please look up the Framework Overview. You can save both using <code>NodeEditor.SaveNodeCanvas</code> 
                and load them with <code>NodeEditor.LoadNodeCanvas</code> and <code>NodeEditor.LoadEditorStates</code>. 
                Take reference from the default NodeEditorWindow to see how exactly these functions are integrated. 
                The function <code>AutoOpenCanvas</code> also shows how to automatically open a canvas by double-clicking it's asset in the Editor.
            </P>
            <br/>
            
            <h4>Bringing the Canvas on screen</h4>
            <P>
                First, you need to make sure that the <u>NodeEditor is initiated </u>using <code>NodeEditor.checkInit</code>, and that there is always a canvas loaded, else creating a new one. 
                Before drawing you'll want to define the rect in which the canvas is drawn. No boundaries are set anymore on where the canvas is set, in how many subgroups, etc. 
                Only the case of <u>modifying the GUI.matrix scale before is not yet supported</u>. You currently must assign the rect to the <u><code>canvasRect</code> property of the EditorState</u>.
                In order to best account for errors, the following drawing statement is embedded in a <u>try-catch block catching only UnityExceptions</u>, unloading the old and creating a new canvas when an error occurs. 
                <u>Draw the canvas</u> by passing both the NodeCanvas and the EditorState into <code>NodeEditor.DrawCanvas</code>, which will behave like an ordinary GUI control in most cases.</P>
            <br/>
            
            <h4>Custom GUISkin</h4>
            <P>
                The GUISkin of the Node Editor can currently only be changed by modifying the <var>NodeEditorGUI.cs</var> source file or by simply replacing the textures. 
                For the future a more extensive and seperated control over the GUISkin is planned.
            </P>
            
            <h3>Framework Overview</h3>
            <P>
                This section aims to bring you a decent overview on how the framework is structured, so you can get to modify it quickly. 
                This does not necessarily include implementation details – code sections that need extra detailing are commented. 
                Also, this section is not only for those planning to get into the code, but for everyone to get an overview what he's working with:)
            </P>
            <br/>
            
            <h4>NodeCanvas and NodeEditorState</h4>
            <P>
            Those two components essentially make up something you can load up into the Editor. Basically, the <u>canvas </u>is the important part with all the <u>nodes and any additional information directly related to the Canvas</u>. 
            In contrary, the <u>EditorState </u>holds all information on the <u>state</u>, or in other words, on how the Canvas is presented. This includes zoom and pan values, selected Nodes, the canvasRect, etc. 
            Not all of these values are actually saved with the asset, though. That structure allows for <u>multiple 'views' on the same Canvas </u>and editing it simultaneously.</P>
            <br/>
            
            <h4>The DrawCanvas function</h4>
            <P>
                This function acts very similar to any other GUI control, with a few exceptions, and is responsible for drawing the Canvas. 
                On the first glance it's just a wrapper for <code>DrawSubCanvas</code>, with the exception that it holds the OverlayGUI and NodeGUISkin code. 
                <code>DrawSubCanvas</code> is used in the future for Nested Canvases, as the name proposes. <br/>
                In the first major block, the background texture is sliced and placd across the screen where needed, accounting for pan and zoom, relative to the rect center. <br/>
                In the function <code>InputEvents</code> all inputs are catched. It's well commented, so no further explanation is necessary here. It accounts for Rects that should be ignored for input. <br/>
                Then, the scale area gets initiated with a call to my custom solution <code>GUIScaleUtility.BeginScale</code>. Any GUI code afterwards is getting scaled appropriately. <br/>
                In the following, everything that needs to be scaled gets drawn, including temporal connections, node transitions, connections, bodies and knobs. <br/>
                Thereafter, the scale area gets closed again with another call to <code>GUIScaleUtility.EndScale</code>. The <code>LateEvents</code> function checks all inputs with secondary priority (after the nodes) 
                just like <code>InputEvents</code> does, in this case it only makes sure the node can only be dragged when not clicking on a control (GUI.hotControl is 0).
            </P>
        </div>
        
        <br/>
        <br/>
        <br/>
        <br/>
        
        <div id="EventsPage" class="page">
            <h2>Events</h2>
            <P>
                (WIP) <br/>
                The Framework supports a multitude of Events which might be important during the editing process. Those Events can either be received 
                by subscribing to the appropriate delegate in the <code>NodeEditorCallbacks</code> class or by extending from <code>NodeEditorCallbackReceiver</code> (which is a MonoBehaviour) 
                and overriding the appropriate method. Both classes can be found in <var>NodeEditorCallbackReceiver.cs</var>. <br/>
                Current Events include:
            </P>
            <ul>
                <li><code>OnEditorStartup ()</code>: The Node Editor gets initiated (can also happen when switching scene or playmode)</li>
                <li><code>OnLoadCanvas (NodeCanvas)</code>: The passed canvas has been loaded (copy)</li>
                <li><code>OnLoadEditorState (NodeEditorState)</code>: The passed editorState has been loaded (copy)</li>
                <li><code>OnSaveCanvas (NodeCanvas)</code>: The passed canvas has been saved (copy)</li>
                <li><code>OnSaveEditorState (NodeEditorState)</code>: The passed editorState has been saved (copy)</li>
                <li><code>OnAddNode (Node)</code>: The passed node has been created or duplicated</li>
                <li><code>OnDeleteNode (Node)</code>: The passed node will get deleted</li>
                <li><code>OnMoveNode (Node)</code>: The passed node has been moved by the user</li>
                <li><code>OnAddConnection (NodeInput)</code>: A new connection has been added to the passed input. If it had a connection before, OnRemoveConnection has been called, too</li>
                <li><code>OnRemoveConnection (NodeInput)</code>: The connection will get removed from this input</li>
                <li><code>OnAddTransition (Transition)</code>: The passed transition has been created</li>
                <li><code>OnRemoveTransition (Transition)</code>: The passed transition will be removed</li>
            </ul>
        </div>
        
        <br/>
        <br/>
        <br/>
        <br/>
        
        <div id="ConclusionPage" class="page">
            <h2>Conclusion</h2>
            <P>
                (WIP) <br/>
                I'm happy that the Node Editor has received so much positive comments and helpful critism since I posted it back in May 2015. <br/>
                Since then a few people took the time and motivation to contribute to the project which I appreciate very much! 
                You can check all contributions out on the <A href="https://github.com/Baste-RainGames/Node_Editor/graphs/contributors">contributions page</A>. 
                But also those who <u>use, test and report bugs are very important</u> for this project. <br/>
                If you wish to <u>contribute</u>, you may take a look at the <u>roadmap as a rough guideline</u> what is planned and how you can help. Of course, own ideas are just as fine. <br/>
                Make sure to post or tell me if you are making an extension using Node Editor, may it be big or small, and notify me about any problems you may encounter:) 
                This is vital to the project! Just make sure to account for the <u>MIT License</u> included with Node Editor. <br/>
                Also, you can always <u>contact Seneral with a PM</u> on the Forums <u>or per Email</u> at lev.gaeher@gmail.com:) <br/>
                I hope this Documentation has helped you understanding the NodeEditor, else feel free to suggest imrovements and ask me!
            </P>
        </div>
        
        <br/>
        <br/>
        <br/>
        <br/>
        <br/>
        <br/>
        <br/>
        <br/>
    </body>
</html>